﻿using Microsoft.AspNetCore.Cryptography.KeyDerivation;
using System;
using System.Security.Cryptography;
using System.Text;

namespace Util.PBKDF2
{
    public static class PBKDF2
    {
        //生成密码
        public static string HashPassword(string value, string salt)
        {
            byte[] valueBytes = KeyDerivation.Pbkdf2(
                password: value,//密码
                salt: Encoding.UTF8.GetBytes(salt),//盐
                prf: KeyDerivationPrf.HMACSHA512,//伪随机函数，这里是SHA-512
                iterationCount: 10000,//迭代次数
                numBytesRequested: 256 / 8);//最后输出的秘钥长度
            return Convert.ToBase64String(valueBytes);
        }
        public static string HashPassword(string password)
        {
            string salt = GenerateSalt(),//盐
            hash = HashPassword(password, salt);
            return $"{hash}{salt}";
        }
        //生成盐
        public static string GenerateSalt()
        {
            byte[] randomBytes = new byte[128 / 8];
            using (var generator = RandomNumberGenerator.Create())
            {
                generator.GetBytes(randomBytes);
                return Convert.ToBase64String(randomBytes);
            }
        }
        //验证
        private static bool Validate(string password, string salt, string hash)
         => HashPassword(password, salt) == hash;
        //验证密码
        public static bool VerifyHashedPassword(string password, string storePassword)
        {
            if (string.IsNullOrEmpty(password))
            {
                throw new ArgumentNullException(nameof(password));
            }

            if (string.IsNullOrEmpty(storePassword))
            {
                throw new ArgumentNullException(nameof(storePassword));
            }
            string[] parts = storePassword.Split('=', 2);
            string salt = parts[1],
            hash = parts[0] + '=';
            return Validate(password, salt, hash);
        }
    }
}
